/**
 * @Author: Jiang Zhongxun
 * @Date: 2024-10-04 12:30:06
 * @FilePath: /Socket/practiceProject/src/db/dbOperation.c
 * @Description: SQLite3数据库操作相关接口
 */
#include "../../include/db/dbOperation.h"

/**
 * 通用的SQL增删改操作接口
 *
 * @param db SQLite3数据库指针
 * @param sql 要执行的SQL语句
 * @param errmsg 输出参数，用于存储错误信息
 * @param operationName 操作名称，用于在错误信息和成功信息中标识操作，如："userInfo"、"logInfo"、"checkInfo"
 * @return 返回0表示成功，非零表示失败
 */
int execOperate(sqlite3 *db, const char *sql, char **errmsg, const char *operationName)
{
    // printf("SQL语句: %s\n", sql);
    int ret = sqlite3_exec(db, sql, NULL, NULL, errmsg);
    if (SQLITE_OK != ret)
    {
        // 使用 fprintf 打印更详细的错误信息
        fprintf(stderr, "%s sqlite3_exec error: %s\n", operationName, *errmsg ? *errmsg : "通用的SQL增删改操作error");
        // 释放错误消息内存
        sqlite3_free(*errmsg);
        return -1;
    }
    // printf("%s sqlite3_exec ok!\n", operationName);
    return 0;
}

/**
 * 通用的SQL条件查询接口
 * 通用的SQL全部查询接口
 * 通用的SQL分页查询接口
 *
 * @param db SQLite3数据库指针
 * @param sql 要执行的SQL语句
 * @param result 指向二维字符串数组的指针。执行成功后，*result 将包含查询结果。每一行数据都是一个字符串数组，每个字符串代表一列的值
 * @param row 指向整数的指针，用于返回结果集中行的数量
 * @param column 指向整数的指针，用于返回结果集中列的数量
 * @param errmsg 输出参数，用于存储错误信息
 * @param operationName 操作名称，用于在错误信息和成功信息中标识操作，如："userInfo"、"logInfo"、"checkInfo"
 * @return *result 成功返回查询的结果集*result，失败返回NULL
 */
char **conditionQuery(sqlite3 *db, const char *sql, char ***result, int *row, int *column, char **errmsg, const char *operationName)
{
    // printf("SQL语句: %s\n", sql);
    if (!db)
    {
        db = databaseInit();
        // fprintf(stderr, "数据库连接无效!\n");
        // return NULL;
    }
    int ret = sqlite3_get_table(db, sql, result, row, column, errmsg);
    if (SQLITE_OK != ret)
    {
        fprintf(stderr, "SQL执行错误码: %d, %s sqlite3_get_table error: %s\n", ret, operationName, *errmsg ? *errmsg : "通用的SQL查询error");
        const char *errMsg = sqlite3_errmsg(db);
        fprintf(stderr, "SQLite 错误信息: %s\n", errMsg);
        sqlite3_free(*errmsg); // 释放错误信息
        *errmsg = NULL;        // 设置为NULL避免多次释放
        return NULL;
    }
    // printf("根据条件共查找到%d条记录, 每一条记录含有%d个字段!\n", *row, *column);
    return *result;
}
